Release 10.1A: OpenEdge Development:
Progress 4GL Handbook


Managing dynamic objects

When you define a static object with the DEFINE statement, Progress knows everything it needs to know about the object at compile time. In addition to setting up the object’s description in r-code at compile time, Progress defines a scope for the object. Chapter 8, "Defining Graphical Objects," discussed object scope. Any defined object has a name, and a reference to that object has to be within its scope. Outside its scope the object name has no meaning and causes a compile-time error.

By contrast, a dynamic object has no particular scope in terms of procedure blocks. It can be referenced and used by any part of the application that has access to its handle from the time it is created until it is deleted. You can explicitly delete an individual dynamic object or you can place that object into a pool of memory where its storage is allocated and then delete the object by deleting its memory pool. It’s especially important to keep in mind that the existence of a dynamic object has nothing to do with the scope of the handle variable you associate it with. For example, look at the following two-line procedure:

DEFINE VARIABLE hButton AS HANDLE     NO-UNDO. 
CREATE BUTTON hButton. 

When the procedure terminates, the hButton variable goes out of scope and you can no longer refer to it. Does this mean that the dynamic button is gone as well? No! The memory Progress allocates for the button is still there, but you have no way of referring to it (or deleting it). It occupies memory until your session ends.

Likewise, you can lose your access to an object by resetting the handle. For example:

DEFINE VARIABLE hButton AS HANDLE       NO-UNDO. 
CREATE BUTTON hButton ASSIGN LABEL = "Lost Button!". 
hButton = ?. 

Oops! You’ve reset your handle variable but the object is still there. You just can’t find it anymore. Or consider this example:

DEFINE VARIABLE hButton  AS HANDLE       NO-UNDO. 
DEFINE VARIABLE iCounter AS INTEGER      NO-UNDO. 
DO iCounter = 1 TO 10: 
    CREATE BUTTON hButton ASSIGN LABEL = "Button #" + STRING(iCounter). 
END. 
MESSAGE hButton:LABEL. 

Figure 18–5 shows the result.

Figure 18–5: Example button message

You’ve just created ten buttons and lost contact with all but the last of them. This is not a good idea. Thus, the first rule of managing dynamic objects is to make sure that you don’t lose track of them. Once you lose a valid handle to a dynamic object you can’t access it and it just sits in memory taking up space.

The next sections describe ways to manage memory and clean up dynamic objects so that this kind of memory leak doesn’t happen in your application.


Copyright © 2005 Progress Software Corporation
www.progress.com
Voice: (781) 280-4000
Fax: (781) 280-4095